// SPDX-License-Identifier: GPL-2.0
/*
 * Copyright (c) 2023 HUAWEI TECHNOLOGIES CO., LTD.
 */
static int vpmem_get_pfn(struct mm_struct *mm, unsigned long vaddr,
			int prot, unsigned long *pfn)
{
	struct vm_area_struct *vma;
	int ret;

	mmap_read_lock(mm);
	vma = find_vma_intersection(mm, vaddr, vaddr + 1);
	ret = follow_pfn(vma, vaddr, pfn);
	mmap_read_unlock(mm);
	return ret;
}

static int vpmem_get_contig_page(struct mm_struct *mm, unsigned long vaddr,
				int prot, unsigned long *pfn, long *contig_pages)
{
	struct vm_area_struct *vma;
	int ret;

	mmap_read_lock(mm);
	vma = find_vma_intersection(mm, vaddr, vaddr + 1);
	ret = follow_pfn(vma, vaddr, pfn);
	if (ret)
		goto out;

	if (vma->vm_file && vma->vm_file->f_op->unlocked_ioctl) {
		*contig_pages = vma->vm_file->f_op->unlocked_ioctl(vma->vm_file,
				VFIO_IOMMU_MAP_DMA, *pfn);
		if (*contig_pages == 0)
			ret = -ENODATA;
	} else {
		ret = -ENOSYS;
	}
out:
	mmap_read_unlock(mm);
	return ret;
}
